import $ from "jquery";
import { HttpClient } from "@/utils/http-client";
import { ProductionBaseResponse } from "@/modules/mixing-process/tyeps/production-base-response";
import { ProductionWorkshopResponse } from "@/modules/mixing-process/tyeps/production-workshop-response";
import { ProductionProcessResponse } from "@/modules/mixing-process/tyeps/production-process-response";
import { DeviceHostResponse } from "@/modules/mixing-process/tyeps/device-host-response";
import { String } from "@/utils/string";

export type CurrentSaveInfo = {
  currentSiteId?: number;
  currentWorkshorpId?: string;
  currentProcessId?: string;
  currentDeviceHostId: string;
  currentDeviceHostName: string;
};

const hbsTemplate = require("./select.hbs");
const selectElement = require("./select-element.hbs");

const url = new URL(window.location.href);
const parameters = new URLSearchParams(url.search);
const mixingProcess = parameters.get("process");

export type SelectOption = { label: string; value: string };
type SelectItem = {
  id: string;
  title: string;
  options: SelectOption[];
  onSelectChanged(newValue: string): void;
};

export type DeviceHostSelectedHandle = (currentHost: SelectOption) => void;
let deviceHostSelected: DeviceHostSelectedHandle = () => {};
export function onDeviceHostSelected(handle: DeviceHostSelectedHandle) {
  deviceHostSelected = handle;
}

function insertItem(item: SelectItem) {
  const htmlString = hbsTemplate(item);
  const element = $(htmlString);

  element.on("change", () => {
    const newValue = element.find("option:selected").val() as string;
    item.onSelectChanged(newValue);
  });

  const bodyElement = $("#input-modal-body");
  bodyElement.append(element);
}

const baseUrl = process.env.DEVICE_OPS_SERVICE_API_BASE_URL;

$(async () => {
  const httpClient = new HttpClient();

  const productionBaseList = await httpClient.getAsync<
    ProductionBaseResponse[]
  >(baseUrl + "/production-bases");

  const siteOptions = productionBaseList.map<SelectOption>((item) => {
    const option: SelectOption = {
      label: item.siteName,
      value: item.id.toString(),
    };
    return option;
  });

  const selectItems: SelectItem[] = [
    {
      id: "currentSiteSelect",
      title: "当前基地",
      options: siteOptions,
      onSelectChanged: async (newValue) => {
        const workshopList = await httpClient.getAsync<
          ProductionWorkshopResponse[]
        >(baseUrl + "/production-bases/" + newValue + "/production-workshops");

        const workshopOptions = workshopList.map((item) => {
          const option: SelectOption = {
            label: item.workshopName,
            value: item.id,
          };
          return option;
        });

        updateOptions("currentWorkshopSelect", workshopOptions);
      },
    },
    {
      id: "currentWorkshopSelect",
      title: "当前车间",
      options: [],
      onSelectChanged: async (newValue) => {
        const processList = await httpClient.getAsync<
          ProductionProcessResponse[]
        >(
          baseUrl +
            "/production-workshops/" +
            newValue +
            "/production-processes"
        );

        const processOptions = processList.map((item) => {
          const option: SelectOption = {
            label: item.processName,
            value: item.id,
          };
          return option;
        });

        updateOptions("currentProcessSelect", processOptions);
      },
    },
    {
      id: "currentProcessSelect",
      title: "当前工序",
      options: [],
      onSelectChanged: async (newValue) => {
        const hostList = await httpClient.getAsync<DeviceHostResponse[]>(
          baseUrl + "/production-processes/" + newValue + "/device-hosts"
        );
        const hostOptions = hostList
          .filter((item) => {
            if (String.isNullOrWhitespace(mixingProcess)) {
              return true;
            } else {
              return item.tag === mixingProcess;
            }
          })
          .map((item) => {
            const option: SelectOption = {
              label: item.deviceHostName,
              value: item.id,
            };
            return option;
          });
        updateOptions("currentHostSelect", hostOptions);
      },
    },
    {
      id: "currentHostSelect",
      title: "设备主机",
      options: [],
      onSelectChanged: async (id) => {
        $("#selectDeviceHostButton")
          .removeClass("btn-secondary")
          .addClass("btn-primary");
        $("#selectDeviceHostButton").removeAttr("disabled");

        const option = selectItems
          .find((item) => item.id === "currentHostSelect")
          ?.options?.find((item) => item.value === id);

        if (option != null) {
          localStorage.setItem(
            "mixing-machine-save-info",
            JSON.stringify({
              currentDeviceHostId: option.value,
              currentDeviceHostName: option.label,
            } as CurrentSaveInfo)
          );
          deviceHostSelected(option);
        }
      },
    },
  ];

  function updateOptions(selectItemId: string, options: SelectOption[]) {
    const htmlElement = selectElement({
      id: selectItemId,
      options: options,
    });
    const element = $(htmlElement);
    $(`#${selectItemId}`).replaceWith(element);
    const item = selectItems.find((item) => item.id === selectItemId);
    if (item != null) {
      item.options = options;
    }
  }

  selectItems.forEach((item) => {
    insertItem(item);
  });
});
